package com.whu.MenuHub.service.Impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.whu.MenuHub.dao.FoodDao;
import com.whu.MenuHub.dao.FoodFlavorDao;
import com.whu.MenuHub.domain.Food;
import com.whu.MenuHub.domain.FoodDTO;
import com.whu.MenuHub.domain.FoodFlavor;
import com.whu.MenuHub.exception.MenuHubException;
import com.whu.MenuHub.service.FoodService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Map;

@Service
public class FoodServiceImpl extends ServiceImpl<FoodDao, Food> implements FoodService {

    @Autowired
    FoodDao foodDao;

    @Autowired
    FoodFlavorDao foodFlavorDao;

    //根据食品id获取食品信息
    @Override
    @Cacheable(cacheNames = "food",key = "#id",condition = "#id!=null")
    public Food getFoodByFoodID(Integer id){
        return foodDao.selectById(id);
    }
    //根据食品名称获取食品信息
    @Override
    @Cacheable(cacheNames = "food",key = "#id",condition = "#id!=null")
    public Food findFoodByFoodName(String foodName){
                return foodDao.findFoodByName(foodName);
    }
    //增加一条食品记录
    @Override
    @Transactional(rollbackFor = MenuHubException.class)
    public Food insertFood(FoodDTO foodDTO) throws MenuHubException{
        try{
            Food food=(Food)foodDTO;
            //插入一条食品信息
            foodDao.insertFood(food);
            //获取到食品口味的对象，更新flavor的foodID
            FoodFlavor flavor=foodDTO.getFoodFlavor();
            flavor.setFoodID(food.getId());
            //将口味信息插入数据库
            foodFlavorDao.insert(flavor);
            return food;
        }catch (Exception e){
            throw new MenuHubException(MenuHubException.ErrorType.INSERT_ERROR,"添加食品信息失败");
        }
    }

    //根据id更新产品信息
    @Transactional(rollbackFor = MenuHubException.class)
    @Override
    @CacheEvict(cacheNames = "food",key = "#foodDTO.id")
    public void updateFoodByID(FoodDTO foodDTO)throws MenuHubException{
        try{
            //修改口味信息
            FoodFlavor flavor=foodDTO.getFoodFlavor();
            flavor.setFoodID(foodDTO.getId());
            foodFlavorDao.updateById(flavor);
            //修改食品基本信息
            Food food=(Food)foodDTO;
            foodDao.updateById(food);
        }catch (Exception e){
            throw new MenuHubException(MenuHubException.ErrorType.UPDATE_ERROR,"修改食品信息失败");
        }
    }

    //删除一条食品信息，考虑外键约束
    @Transactional(rollbackFor = MenuHubException.class)
    @Override
    @CacheEvict(cacheNames = "food",key = "#id")
    public void deleteFoodByID(Integer id)throws MenuHubException{
        try{
            if(foodFlavorDao.selectById(id)!=null){
                //先删除口味偏好表中的信息
                foodFlavorDao.deleteById(id);
            }
            foodDao.deleteById(id);
        }catch (Exception e){
            throw new MenuHubException(MenuHubException.ErrorType.DELETE_ERROR,"删除食品信息失败");
        }
    }

    //分页查找食品信息
    public IPage<Food> findFoods(Map<String, Object> condition, Integer pageNum, Integer pageSize){
        IPage page = new Page(pageNum, pageSize);
        QueryWrapper<Food> qw = new QueryWrapper<>();
        qw.like(condition.containsKey("keyword"), "foodName", condition.get("keyword"));
        qw.lt(condition.containsKey("maxPrice"), "price", condition.get("maxPrice"));
        qw.ge(condition.containsKey("minPrice"), "price", condition.get("minPrice"));
        qw.eq(condition.containsKey("label"), "label", condition.get("label"));
        if(condition.containsKey("orderField")){
            String orderField=condition.get("orderField").toString();
            //当排序的类型不为空，且为降序的时候，按照降序排列
            if(condition.containsKey("orderType")&&condition.get("orderType").equals("ASC")){
                qw.orderByAsc(orderField);
            }
            //当排序的类型为空，或指明升序，则按升序排列
            else{
                qw.orderByDesc(orderField);
            }
        }
        return foodDao.findFoods(page, qw);
    }

    //商家获取全部的食品信息
    @Override
    public List<Food> findAllFood(Map<String, Object> condition){
        QueryWrapper<Food> qw = new QueryWrapper<>();
        qw.like(condition.containsKey("keyword"), "foodName", condition.get("keyword"));
        qw.lt(condition.containsKey("maxPrice"), "price", condition.get("maxPrice"));
        qw.ge(condition.containsKey("minPrice"), "price", condition.get("minPrice"));
        qw.eq(condition.containsKey("label"), "label", condition.get("label"));
        if(condition.containsKey("orderField")){
            String orderField=condition.get("orderField").toString();
            //当排序的类型不为空，且为降序的时候，按照降序排列
            if(condition.containsKey("orderType")&&condition.get("orderType").equals("ASC")){
                qw.orderByAsc(orderField);
            }
            //当排序的类型为空，或指明升序，则按升序排列
            else{
                qw.orderByDesc(orderField);
            }
        }
        return foodDao.selectList(qw);
    }
    //获取全部食物信息
    @Override
    public List<Food> getAllFood(){
        QueryWrapper<Food> qw = new QueryWrapper<>();
        return foodDao.selectList(qw);
    }

    //获取近7日销量最高的食物
    @Override
    public List<Food> getHotFoodWithin7Day(){
        return foodDao.getHotFoodWithin7Day();
    }
}
